import { Service } from 'egg';
import { RESULT_CODE } from '../utils/constants/code';

type OrderItemInput = { dish_id: number; quantity: number };
type OrderStatus = 'pending' | 'accepted' | 'rejected' | 'cancelled';

export default class ExclusiveRestaurantOrderService extends Service {
  // 创建订单（根据菜品推导餐厅，要求同一餐厅）
  async createOrder(items: OrderItemInput[], remark: string) {
    const { ctx } = this;
    const userId = ctx.state.user.user_id;
    if (!Array.isArray(items) || items.length === 0) {
      ctx.throw(RESULT_CODE.FAIL, '订单菜品不能为空');
    }

    // 查询菜品，校验归属同一餐厅、有效性
    const dishIds = items.map(i => i.dish_id);
    const dishes = await ctx.model.ExclusiveDish.findAll({ where: { id: dishIds } });
    if (dishes.length !== dishIds.length) ctx.throw(RESULT_CODE.FAIL, '存在无效菜品');

    const restaurantIds = new Set(dishes.map((d: any) => d.restaurant_id));
    if (restaurantIds.size !== 1) ctx.throw(RESULT_CODE.FAIL, '订单必须来自同一餐厅');
    const restaurant_id = dishes[0] && (dishes[0] as any).restaurant_id;

    // 校验餐厅状态（需为已审核）
    const restaurant = await ctx.model.ExclusiveRestaurant.findOne({
      where: { id: restaurant_id, status: 'approved' },
    });
    if (!restaurant) ctx.throw(RESULT_CODE.FAIL, '专属餐厅不存在或未通过审核');

    // 受邀校验：仅被该餐厅接受邀请的用户可下单
    const acceptedInvite = await ctx.model.ExclusiveRestaurantInvite.findOne({
      where: { restaurant_id, invitee_id: userId, status: 'accepted' },
    });
    if (!acceptedInvite) ctx.throw(403, '仅受邀并已接受的用户可下单');

    // 组装订单项快照
    const dishMap = new Map<number, any>();
    dishes.forEach((d: any) => dishMap.set(d.id, d));
    const orderItems = items.map((it) => {
      const d = dishMap.get(it.dish_id);
      const price = Number(d.price || 0);
      const quantity = Number(it.quantity || 1);
      if (quantity <= 0) ctx.throw(RESULT_CODE.FAIL, '数量不合法');
      return { dish_id: d.id, name: d.name, price, pictures: d.pictures, quantity };
    });

    // 创建订单与订单项（事务）
    const result = await ctx.model.transaction(async (t) => {
      const order = await ctx.model.ExclusiveOrder.create({
        restaurant_id,
        user_id: userId,
        status: 'pending',
        remark: remark || '',
      }, { transaction: t });

      // 批量创建订单项
      const rows = await ctx.model.ExclusiveOrderItem.bulkCreate(
        orderItems.map(oi => ({ ...oi, dish_id: oi.dish_id, order_id: (order as any).id })),
        { transaction: t }
      );

      return {
        order,
        items: rows,
      };
    });

    return result;
  }

  // 取消订单（仅下单用户，且 pending 才能取消）
  async cancelOrder(id: number) {
    const { ctx } = this;
    const userId = ctx.state.user.user_id;
    const order = await ctx.model.ExclusiveOrder.findByPk(id);
    if (!order) ctx.throw(RESULT_CODE.FAIL, '订单不存在');
    if ((order as any).user_id !== userId) ctx.throw(403, '无权取消该订单');
    if ((order as any).status !== 'pending') ctx.throw(RESULT_CODE.FAIL, '当前状态不可取消');

    await (order as any).update({ status: 'cancelled' as OrderStatus });
    return { message: '取消成功' };
  }

  // 处理订单（餐厅老板：pending -> accepted/rejected）
  async processOrder(id: number, status: 'accepted' | 'rejected') {
    const { ctx } = this;
    const userId = ctx.state.user.user_id;

    const order = await ctx.model.ExclusiveOrder.findByPk(id);
    if (!order) ctx.throw(RESULT_CODE.FAIL, '订单不存在');
    if ((order as any).status !== 'pending') ctx.throw(RESULT_CODE.FAIL, '当前状态不可处理');

    // 餐厅归属校验：订单餐厅必须属于当前用户
    const restaurant = await ctx.model.ExclusiveRestaurant.findOne({
      where: { id: (order as any).restaurant_id, user_id: userId, status: 'approved' },
    });
    if (!restaurant) ctx.throw(403, '无权处理该订单');

    await (order as any).update({ status });
    return { message: '处理成功' };
  }

  // 订单列表
  // scope=customer：本人作为顾客的订单
  // scope=restaurant：当前用户餐厅收到的订单
  async listOrders(query: { scope?: 'customer' | 'restaurant'; page?: number; limit?: number; status?: OrderStatus }) {
    const { ctx } = this;
    const userId = ctx.state.user.user_id;
    const { scope = 'customer', page = 1, limit = 10, status } = query as any;

    const where: any = {};
    if (scope === 'customer') {
      where.user_id = userId;
    } else {
      const restaurant = await ctx.model.ExclusiveRestaurant.findOne({
        where: { user_id: userId, status: 'approved' },
      });
      if (!restaurant) ctx.throw(RESULT_CODE.FAIL, '专属餐厅不存在或未通过审核');
      where.restaurant_id = (restaurant as any).id;
    }
    if (status) where.status = status;

    const offset = (Number(page) - 1) * Number(limit);

    const { count, rows } = await ctx.model.ExclusiveOrder.findAndCountAll({
      where,
      order: [['created_at', 'DESC']],
      limit: Number(limit),
      offset,
      include: [
        { model: ctx.model.ExclusiveOrderItem, as: 'order_dishs' },
        { model: ctx.model.User, as: 'user' },
      ],
    });

    // 处理图片链接
    const newRow = rows.map(order => {
      const orderData = order!.toJSON() as any;
      orderData?.order_dishs?.forEach(it => {
        it.imgList = it?.pictures?.split(',')?.map(i => this.config.host + i) || []
      })
      return orderData;
    });

    return {
      list: newRow,
      total: count,
      page: Number(page),
      limit: Number(limit),
    };
  }
}